package u.hnx.admin.utils;

import cn.hutool.core.util.ObjectUtil;
import cn.hutool.core.util.StrUtil;
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.ObjectMapper;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.validation.ConstraintViolation;
import jakarta.validation.Validation;
import org.springframework.http.MediaType;
import org.springframework.util.StreamUtils;
import u.hnx.admin.exception.sys.UserBlankException;
import u.hnx.admin.query.user.LoginQuery;
import u.hnx.admin.security.api.SecurityVerifyAPI;

import java.io.IOException;
import java.util.HashMap;
import java.util.Map;
import java.util.Optional;
import java.util.Set;

public class RequestParamsWapperUtil implements SecurityVerifyAPI {
    private static final  ObjectMapper objectMapper = new ObjectMapper();
    public static LoginQuery getRequestAttributes(HttpServletRequest request) throws IOException {
        String id = RequestContextHelper.getRequestId();
        if(StrUtil.isNotBlank(id)){
            return RequestContextHelper.getContext();
        }
        else {
            String reqKey = RequestContextHelper.generateRequestId();
            RequestContextHelper.setRequestId(reqKey);
            RequestContextHelper.setRequest(request);
            LoginQuery loginQuery = getRequestParam(request);
            RequestContextHelper.setContext(loginQuery);
            Set<ConstraintViolation<LoginQuery>> validate = Validation.buildDefaultValidatorFactory().getValidator().validate(loginQuery);
            if(ObjectUtil.isNotEmpty(validate) && validate.size()>0){
                throw new UserBlankException(validate.stream().findFirst().get().getMessage());
            }
            return loginQuery;
        }
    }
    private static LoginQuery getRequestParam(HttpServletRequest request) throws IOException {
        if (request.getContentType().equalsIgnoreCase(MediaType.APPLICATION_JSON_VALUE) || request.getContentType().equalsIgnoreCase(MediaType.APPLICATION_JSON_UTF8_VALUE)) {
            byte[] bytes = StreamUtils.copyToByteArray(request.getInputStream());
            Optional.ofNullable(bytes).orElseThrow(() -> new UserBlankException(LOGIN_REQUEST_NONE));
            return objectMapper.readValue(bytes, LoginQuery.class);
        }
        return   readRequestParam(request);
    }
    private static LoginQuery readRequestParam(HttpServletRequest request) {
        try {
            Map<String, String[]> paramMap = request.getParameterMap();
            Optional.ofNullable(paramMap).orElseThrow(() -> new UserBlankException(LOGIN_REQUEST_NONE));
            return objectMapper.readValue(readValueToString(paramMap), LoginQuery.class);
        }catch (Exception ex){
            throw new RuntimeException(ex.getMessage());
        }
    }
    private static String readValueToString(Map<String, String[]> map){
        Map<String, String> stringMap = new HashMap<>();
        for (Map.Entry<String, String[]> entry : map.entrySet()) {
            String key = entry.getKey();
            String[] values = entry.getValue();
            stringMap.put(key, values[0]);
        }
        try {
            return objectMapper.writeValueAsString(stringMap);
        } catch (JsonProcessingException e) {
            throw new RuntimeException(e);
        }
    }
}
